package earogya.ehr.medical_records.ws;

import java.io.IOException;

import org.hibernate.HibernateException;

import ca.uhn.hl7v2.HL7Exception;
import ca.uhn.hl7v2.model.DataTypeException;
import ca.uhn.hl7v2.model.Message;
import ca.uhn.hl7v2.model.v251.segment.*;
import ca.uhn.hl7v2.model.v251.datatype.XAD;
import ca.uhn.hl7v2.model.v251.datatype.XPN;
import ca.uhn.hl7v2.model.v251.datatype.XTN;
import ca.uhn.hl7v2.model.v251.message.*;
import ca.uhn.hl7v2.parser.DefaultXMLParser;
import ca.uhn.hl7v2.parser.EncodingNotSupportedException;
import ca.uhn.hl7v2.parser.GenericParser;
import ca.uhn.hl7v2.parser.Parser;
import ca.uhn.hl7v2.parser.PipeParser;
import earogya.ehr.medical_records.messages.*;


public class HL7MessageHandler {

	public String parser(String message) throws HL7Exception, IOException{
		Parser p = new GenericParser();
		//PipeParser p=new PipeParser();
	//	Parser p=new DefaultXMLParser();
		String ack=null;
		 Message hapiMsg;
		 try {
		 // The parse method performs the actual parsing
			 hapiMsg = p.parse(message);
		 	 MSH mshSegment=(MSH)hapiMsg.get("MSH");

		 	 String msgType=mshSegment.getMessageType().getMessageCode().getValue();

			 String msgTrigger = mshSegment.getMessageType().getTriggerEvent().getValue();
			 ack=identifyMessage(msgType, msgTrigger, hapiMsg);
			 System.out.println(msgType+" "+msgTrigger);
		 } catch (EncodingNotSupportedException e) {
			 e.printStackTrace();
		 } catch (HL7Exception e) {
			 e.printStackTrace();
		 } catch (HibernateException e) {
			 e.printStackTrace();
		} catch (IOException e) {
			 e.printStackTrace(); 
		}	
		 return ack;
	}
	
	private String identifyMessage(String messageCode, String triggerEvent, Message hapiMsg) throws HibernateException, IOException, HL7Exception{
		String ack=null;
		if(messageCode.equals("ADT")){
			ack=this.identifyTriggerEventForADT(triggerEvent, hapiMsg);
		}else if(messageCode.equals("ADR")){
			ack=this.identifyTriggerEventForADR(triggerEvent, hapiMsg);
		}else if(messageCode.equals("ACK")){
			this.identifyTriggerEventForACK(triggerEvent);
		}else if(messageCode.equals("QRY")){
			ack=this.identifyTriggerEventForQRY(triggerEvent, hapiMsg);
		}else{
			System.out.println("Unexpected trigger event");
		}
		return ack;
	}
	
	private String identifyTriggerEventForADT(String triggerEvent, Message hapiMsg) throws HibernateException, IOException, HL7Exception{
		String ack=null;
		if(triggerEvent.equals("A01")){
			 ADT_A01 adtMsg = (ADT_A01)hapiMsg;
			 ADT_01_Handler handler=new ADT_01_Handler(adtMsg);
			 ack=handler.manageMessage();
		}
		else if(triggerEvent.equals("A02")){
			 ADT_A02 adtMsg = (ADT_A02)hapiMsg;
			 ADT_02_Handler handler=new ADT_02_Handler(adtMsg);
			 ack=handler.manageMessage();
		}
		else if(triggerEvent.equals("A03")){
			 ADT_A03 adtMsg = (ADT_A03)hapiMsg;
			 ADT_03_Handler handler=new ADT_03_Handler(adtMsg);
			 ack=handler.manageMessage();
		}
		else if(triggerEvent.equals("A08")){
			ADT_A01 adtMsg = (ADT_A01)hapiMsg; //both A01 and A08 have the same segments
			ADT_08_Handler handler=new ADT_08_Handler(adtMsg);
			ack=handler.manageMessage();
		}
		else if(triggerEvent.equals("A11")){
			ADT_A09 adtMsg = (ADT_A09)hapiMsg; //in hapi parser both ADT_A09 and ADT_A11 are equal.
			ADT_11_Handler handler=new ADT_11_Handler(adtMsg);
			ack=handler.manageMessage();
		}
		else if(triggerEvent.equals("A17")){
			ADT_A17 adtMsg = (ADT_A17)hapiMsg;
			ADT_17_Handler handler=new ADT_17_Handler(adtMsg);
			ack=handler.manageMessage();
		}
		else if(triggerEvent.equals("A34")){
			ADT_A30 adtMsg = (ADT_A30)hapiMsg;
			ADT_34_Handler handler=new ADT_34_Handler(adtMsg);
			ack=handler.manageMessage();
		}
		else if(triggerEvent.equals("A61")){
			ADT_A61 adtMsg=(ADT_A61)hapiMsg;
			ADT_61_Handler handler=new ADT_61_Handler(adtMsg);
			ack=handler.manageMessage();
		}
		else{
			System.out.println("Unexpected message");
		}
		return ack;
	}
	
	private void identifyTriggerEventForACK(String triggerEvent){
		
	}
	
	private String identifyTriggerEventForADR(String triggerEvent, Message hapiMsg) throws HL7Exception, IOException{
		String ack=null;
		if(triggerEvent.equals("A19")){
			 ADR_A19 adtMsg = (ADR_A19)hapiMsg;
			 ADR_19_Handler handler=new ADR_19_Handler(adtMsg);
			 ack=handler.manageMessage();
		}
		else{
			
		}
		return ack;
	}
	
	private String identifyTriggerEventForQRY(String triggerEvent, Message hapiMsg) throws HL7Exception, IOException{
		String ack=null;
		QRY_A19 qryMsg=(QRY_A19)hapiMsg;
		QRY_A19_Handler handler=new QRY_A19_Handler(qryMsg);
		ack=handler.handleMessage();
		return ack;
	}
	

	public static void main(String[] args) throws HL7Exception, IOException{
		/*String msg = "MSH|^~\\&|HIS|RIH|EKG|EKG|199904140038||ADT^A01||P|2.5.1\r"
			// +"PID|0001|00009874|00001122|A00977|SMITH^JOHN^M|MOM|19581119|F|NOTREAL^LINDA^M|C|564 SPRING ST^^NEEDHAM^MA^02494^US|0002|(818)565-1551|(425)828-3344|E|S|C|0000444444|252-00-4414||||SA|||SA||||NONE|V1|0001||D.ER^50A^M110^01|ER|P00055|11B^M011^02|070615^BATMAN^GEORGE^L|555888^NOTREAL^BOB^K^DR^MD|777889^NOTREAL^SAM^T^DR^MD^PHD|ER|D.WT^1A^M010^01|||ER|AMB|02|070615^NOTREAL^BILL^L|ER|000001916994|D||||||||||||||||GDD|WA|NORM|02|O|02|E.IN^02D^M090^01|E.IN^01D^M080^01|199904072124|199904101200|199904101200||||5555112333|||666097^NOTREAL^MANNY^P\r"
			 +"NK1|2|silva^chamendri|SPOUSE|&2nd lane&4^^Nelumpura South^Ratmalana^^Sri Lanka^|(900)485-5344^^^cjasdb@gjsd.sd^^^011232423||\r"
			 +"PV1|||||145||||777889||||||||070615|||||||||||||||||||||||6_30|02|||199904111200|||||||||\r"
			 +"OBX||ST|||high body temperature|||||||||201105221045||777889|\r"
			 +"DG1||||fever|201105212221|||||||||||777889||||";*/
		/*String msg="MSH|^~\\&|REGADT|MCM|IFENG||199112311501||ADT^A04^ADT_A01|000001|P|2.5||| EVN|A04|199901101500|199901101400|01||199901101410 PID|||191919^^SAMPLE^MR~371-66-9256^^^USSSA^SS|253763|SAMPLE^JAMES^A||19560129|M|||999 SAMPLELIN^^ISHSAMPLE^MI^49849^\"\"^||800)485-5344|(888)485-5344||S^^HL70002|C^^HL70006|10199925^^^SAMPLE^AN|371-66-9256|| NK1|1|SAMPLE^ELLEN|SPOUSE^^HL70063|171 SAMPLELIN^^ISHSAMPLE^MI^49849^\"\"^|(900)485-5344|(900)545-1234~(900)545-1200|EC1^FIRST EMERGENCY CONTACT^HL70131 NK1|2|SAMPLE^MARYLOU|MOTHER^^HL70063|300 SAMPLELIN^^ISHSAMPLE^MI^49849^\"\"^|(900)485-5344|(900)545-1234~(900)545-1200|EC2^SECOND EMERGENCY CONTACT^HL70131 NK1|3 NK1|4|||123 SAMPLERY WAY^^ISHSAMPLE^MI^49849^\"\"^||(800)545-1200|EM^EMPLOYER^HL70131|19940605||PROGRAMMER|||SAMPLE SOFTWARE COMPANY PV1||O|O/R||||0148^SAMPLEN,JAMES|0148^SAMPLEN,JAMES||AMB|||||||0148^SAMPLEN,JAMES|S|1400|A|||||||||||||||||||SAMPLE|||||199501101410| PV2||||||||199901101400|||||||||||||||||||||||||199901101400 ROL||AD|CP^^HL70443|0148^SAMPLEN,JAMES OBX||NM|3141-9^BODY WEIGHT^LN||62|kg|||||F OBX||NM|3137-7^HEIGHT^LN||190|cm|||||F DG1|1|19|R63.4^LOSS OF WEIGHT^I10|||00| GT1|1||SAMPLE^JAMES^\"\"^\"\"^\"\"^\"\"^||171 SAMPLELIN^^ISHSAMPLE^MI^49849^\"\"^|(800)485-5344|            (800)485-5344      ||||SE^SELF^HL70063|371-66-925||||SAMPLE AUTO PLACE|171 SAMPLELIN^^ISHSAMPLE^MI^49849^\"\"|(800)485-5344| IN1|0|0^HL70072|BC1|BLUE CROSS|171 SAMPLELIN^^ISHSAMPLE^M149849^\"\"^||(900)485-5344|90||||||50 OK| ";*/
		
		String msgA02="MSH|^~\\&|AccMgr|1|||20050110114442||ADT^A02|59910287|P|2.5.1||| \r" +
				"EVN|A02|20050110114442|||||\r " +
				"PID|250|22|10006579^^^1^MRN^1||DUCK^DONALD^D||19241010|M||1|111^DUCK ST^^FOWL^CA^999990000^^M|1|8885551212|8885551212|1|2||40007716^^^AccMgr^VN^1|123121234|||||||||||NO \r" +
				"PV1|1|I|IN1^214^1^1^^^S^^AAA^|3||PREOP^101^^^^^^^AAA^|37^DISNEY^WALT^^^^^^AccMgr^^^^CI||23|01||||1|||37^DISNEY^WALT^^^^^^AccMgr^^^^CI|2|40007716^^^AccMgr^VN|4|||||||||||||||||||1||I|||20050110045253||||||";

		
		HL7MessageHandler h=new HL7MessageHandler();
		h.parser(msgA02);
		//String msg=h.createMessage();
		//System.out.println(msg);
		/*String ack=h.parser(msg);
		System.out.println(ack);*/
		
	}
	
	private String createMessage() throws HL7Exception{
		QRY_A19 qry=new QRY_A19();
		MSH mshSegment = qry.getMSH();
		mshSegment.getFieldSeparator().setValue("|");
		mshSegment.getEncodingCharacters().setValue("^~\\&");
		mshSegment.getDateTimeOfMessage().getTime().setValue("200701011539");
		mshSegment.getMessageType().getMsg1_MessageCode().setValue("QRY");
		mshSegment.getMessageType().getTriggerEvent().setValue("A19");
		mshSegment.getVersionID().getVersionID().setValue("2.5.1");
		
		qry.getQRD().getWhoSubjectFilter(0).getIDNumber().setValue("348");
		qry.getQRD().getWhatSubjectFilter(0).getText().setValue("guardian");
		String message=qry.getMessage().encode();
		return message;
	}
}
